class Vue {
  constructor(options) {
    // 存一些用到的值
    this.$options = options || {};
    this.$data = options.data || {};
    this.$el = typeof options.el === 'string' ? document.querySelector(options.el) : options.el;
    // 将data中的值通过getter和setter，注入到Vue实例中
    this._proxyData(this.$data)
    // 将$data中的值变为响应式，实际的操作在这里完成。
    new Observer(this.$data)
    // 编译模板
    new Compiler(this)
  }
  _proxyData($data) {
    Object.keys($data).forEach(key => {
      Object.defineProperty(this, key, {
        enumerable: true,
        configurable: true,
        get() {
          // 这里访问$data中的值，会触发new observer函数中的get
          return  $data[key]
        },
        set(value) {
          if(value === $data[key]) {
            return
          }
          // 这里会触发new Observer 中的set从而更新视图
          $data[key] = value;
        }
      })
    })
  }
}